package com.example.service;

import com.alibaba.fastjson.JSONObject;
import com.example.base.domain.*;
import com.example.base.mapper.*;
import com.example.util.GetDateUtils;
import com.example.util.HttpURLConnectionUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;


@Component
public class ZhiHuService {

    @Resource
    private ZhiHuAnswerMapper zhiHuAnswerMapper;

    @Resource
    private ZhiHuArticleMapper zhiHuArticleMapper;

    @Resource
    private ZhiHuExtMapper zhiHuExtMapper;

    @Resource
    private ZhiHuTrendMapper zhiHuTrendMapper;

    @Resource
    private ZhiHuFansMapper zhiHuFansMapper;

    @Resource
    private UserMapper userMapper;

    @Resource
    private MailService mailService;

    private static Logger logger = LoggerFactory.getLogger(ZhiHuService.class);

    /**
     * 单知乎账号数据同步
     * @param userKey
     */
    public void syncZhiHuJobForUser(String userKey) {
        UserExample example = new UserExample();
        example.createCriteria().andUserNameEqualTo(userKey);
        List<User> userList = userMapper.selectByExample(example);
        Optional.ofNullable(userList).orElse(new ArrayList<>()).forEach(user -> {
            getArticle(user);
            getAnswer(user);
            getAccountTrend(user);
            getAccountFans(user);
        });
    }

    /**
     * 同步所有用户数据
     */
    public void syncZhiHuJob() {
        UserExample example = new UserExample();
        List<User> userList = userMapper.selectByExample(example);

        for (User user : userList) {
            int exceptionCount = 0;
            try {
                // 同步用户的知乎文章数据
                getArticle(user);
            } catch (Exception exception) {
                logger.info(user.getUserName() + "同步用户的知乎文章数据失败:" + exception.getMessage());
                exceptionCount++;
            }
            try {
                // 同步用户的回答数据并保存
                getAnswer(user);
            } catch (Exception exception) {
                logger.info(user.getUserName() + "同步用户的回答数据失败:" + exception.getMessage());
                exceptionCount++;
            }
            try {
                // 同步用户阅读趋势
                getAccountTrend(user);
            } catch (Exception exception) {
                logger.info(user.getUserName() + "同步用户阅读趋势失败:" + exception.getMessage());
                exceptionCount++;
            }
            try {
                // 同步粉丝数据
                getAccountFans(user);
            } catch (Exception exception) {
                logger.info(user.getUserName() + "同步粉丝数据失败:" + exception.getMessage());
                exceptionCount++;
            }
            if (exceptionCount > 3) {
                // 查询失败时，说明cookie过期或用户信息错误，发送邮件提醒
                sendEmail(user);
            }
        }
    }

    /**
     * 获取用户的回答数据并保存
     * @param user
     */
    private void getAnswer(User user) {
        try {
            String userName = StringUtils.isEmpty(user.getShowName()) ? user.getUserName() : user.getShowName();
            String ck = user.getCookie();
            /*调用知乎接口获取文章csv数据*/
            Map<String, String> header = HttpURLConnectionUtil.auth(ck);
            List<ZhiHuAnswer> zhiHuAnswerList = HttpURLConnectionUtil.doGetAnswer("https://www.zhihu.com/api/v4/creators/analysis/realtime/content/list?type=answer&format=csv", header);

            Optional.ofNullable(zhiHuAnswerList).orElse(new ArrayList<>()).forEach(answer -> {
                try {
                    // 获取当前日期
                    String today = GetDateUtils.getDate2String("", new Date());

                    // 获取回答数据
                    ZhiHuAnswerExample example = new ZhiHuAnswerExample();
                    example.createCriteria().andUserEqualTo(userName).andLinkEqualTo(answer.getLink());
                    List<ZhiHuAnswer> answerList = zhiHuAnswerMapper.selectByExample(example);
                    if (!CollectionUtils.isEmpty(answerList) && answerList.stream().anyMatch(bo -> GetDateUtils.getDate2String("", bo.getCreatedTime()).equals(today))) {
                        List<ZhiHuAnswer> existAnswerList = answerList.stream().filter(bo -> GetDateUtils.getDate2String("", bo.getCreatedTime()).equals(today)).collect(Collectors.toList());
                        for (int i = 0; i < existAnswerList.size(); i++) {
                            ZhiHuAnswer zhiHuAnswer = existAnswerList.get(i);
                            if (i == 0) {
                                answer.setId(zhiHuAnswer.getId());
                                answer.setCreatedTime(new Date());
                                ZhiHuAnswerExample updateExample = new ZhiHuAnswerExample();
                                updateExample.createCriteria().andIdEqualTo(zhiHuAnswer.getId());
                                zhiHuAnswerMapper.updateByExampleSelective(answer, updateExample);
                            } else {
                                ZhiHuAnswerExample updateExample = new ZhiHuAnswerExample();
                                updateExample.createCriteria().andIdEqualTo(zhiHuAnswer.getId());
                                zhiHuAnswerMapper.deleteByExample(updateExample);
                            }
                        }
                    } else {
                        answer.setId(UUID.randomUUID().toString());
                        answer.setCreatedTime(new Date());
                        answer.setUser(userName);
                        zhiHuAnswerMapper.insert(answer);
                    }
                } catch (Exception exception) {
                    logger.error(exception.getMessage(), exception);
                }
            });
        } catch (Exception exception) {
            copyYesterdayAnswerForUser(user.getUserName());
            throw new RuntimeException("GetAnswer Exception:" + exception.getMessage() + ";异常用户：" + JSONObject.toJSONString(user));
        }
    }

    private void copyYesterdayAnswerForUser(String userName) {
        String today = GetDateUtils.getDate2String("", new Date());

        List<ZhiHuAnswer> zhiHuAnswerList = zhiHuExtMapper.getYesterdayAnswerByUser(userName, today);
        if (!CollectionUtils.isEmpty(zhiHuAnswerList)) {
            for (ZhiHuAnswer answer : zhiHuAnswerList) {
                if (zhiHuExtMapper.countArticleByExample(userName, answer.getLink(), today) == 0) {
                    answer.setId(UUID.randomUUID().toString());
                    answer.setCreatedTime(new Date());
                    zhiHuAnswerMapper.insert(answer);
                }
            }
        }
    }

    public void sendEmail(User user) {
        if (!StringUtils.isEmpty(user.getEmail())) {
            mailService.sendSimpleEmail("知乎账号cookie失效，请及时更新", "您的知乎账号cookie已失效，请获取新的cookie进行更新，将新的cookie发送给赵乾，失效用户信息：" + user, user.getEmail());
        }
        mailService.sendSimpleEmail("知乎账号cookie失效，请及时更新", "您的知乎账号cookie已失效，请获取新的cookie进行更新，将新的cookie发送给赵乾，失效用户信息：" + user, "qian.zhao@fit2cloud.com");
    }

    /**
     * 获取单用户的文章数据并保存
     * @param user
     */
    private void getArticle(User user) {
        try {
            String userName = StringUtils.isEmpty(user.getShowName()) ? user.getUserName() : user.getShowName();
            String ck = user.getCookie();

            /*调用知乎接口获取文章csv数据*/
            Map<String, String> header = HttpURLConnectionUtil.auth(ck);
            List<ZhiHuArticle> zhiHuArticleList = HttpURLConnectionUtil.doGetArticle("https://www.zhihu.com/api/v4/creators/analysis/realtime/content/list?type=article&format=csv", header);

            Optional.ofNullable(zhiHuArticleList).orElse(new ArrayList<>()).forEach(article -> {
                try {
                    // 获取当前日期
                    String today = GetDateUtils.getDate2String("", new Date());

                    // 查询当前文章是否存在
                    ZhiHuArticleExample example = new ZhiHuArticleExample();
                    example.createCriteria().andUserEqualTo(userName).andLinkEqualTo(article.getLink());
                    List<ZhiHuArticle> zhiHuArticles = zhiHuArticleMapper.selectByExample(example);

                    // 若文章已存在，则更新，并删除多余的
                    if (!CollectionUtils.isEmpty(zhiHuArticles) && zhiHuArticles.stream().anyMatch(bo -> GetDateUtils.getDate2String("", bo.getCreatedTime()).equals(today))) {
                        List<ZhiHuArticle> existsArticles = zhiHuArticles.stream().filter(bo -> GetDateUtils.getDate2String("", bo.getCreatedTime()).equals(today)).collect(Collectors.toList());
                        for (int i = 0; i < existsArticles.size(); i++) {
                            ZhiHuArticle zhiHuArticle = existsArticles.get(i);
                            if (i == 0) {
                                article.setId(zhiHuArticle.getId());
                                article.setCreatedTime(new Date());
                                ZhiHuArticleExample updateExample = new ZhiHuArticleExample();
                                updateExample.createCriteria().andIdEqualTo(zhiHuArticle.getId());
                                zhiHuArticleMapper.updateByExampleSelective(article, updateExample);
                            } else {
                                ZhiHuArticleExample updateExample = new ZhiHuArticleExample();
                                updateExample.createCriteria().andIdEqualTo(zhiHuArticle.getId());
                                zhiHuArticleMapper.deleteByExample(updateExample);
                            }
                        }
                    } else {
                        // 若文章不存在则插入
                        article.setId(UUID.randomUUID().toString());
                        article.setCreatedTime(new Date());
                        article.setUser(userName);
                        zhiHuArticleMapper.insert(article);
                    }
                } catch (Exception exception) {
                    logger.error("同步文章失败：" + JSONObject.toJSONString(article) + "；异常信息：" + exception.getMessage());
                }
            });
        } catch (Exception exception) {
            // 查询失败时，说明cookie过期或用户信息错误，发送邮件提醒
            copyYesterdayArticleForUser(user.getUserName());
            throw new RuntimeException("GetArticle Exception:" + exception.getMessage() + ";异常用户：" + JSONObject.toJSONString(user));
        }
    }

    private void copyYesterdayArticleForUser(String userName) {
        String today = GetDateUtils.getDate2String("", new Date());
        List<ZhiHuArticle> zhiHuArticleList = zhiHuExtMapper.getYesterdayArticleByUser(userName, today);
        if (!CollectionUtils.isEmpty(zhiHuArticleList)) {
            for (ZhiHuArticle article : zhiHuArticleList) {
                if (zhiHuExtMapper.countArticleByExample(userName, article.getLink(), today) == 0) {
                    article.setId(UUID.randomUUID().toString());
                    article.setCreatedTime(new Date());
                    zhiHuArticleMapper.insert(article);
                }
            }
        }
    }

    /**** 获取数据趋势数据 *****/
    public void getAccountTrend(User user) {
        // https://www.zhihu.com/api/v4/creators/analysis/realtime/member/daily?tab=all&start=2022-10-26&end=2022-11-01&format=csv
        try {
            String userName = StringUtils.isEmpty(user.getShowName()) ? user.getUserName() : user.getShowName();
            String ck = user.getCookie();
            /*调用知乎接口获取文章csv数据*/
            Map<String, String> header = HttpURLConnectionUtil.auth(ck);
            List<ZhiHuTrend> zhiHuTrendList = HttpURLConnectionUtil.doGetTrend("https://www.zhihu.com/api/v4/creators/analysis/realtime/member/daily?tab=all&start=" + GetDateUtils.getBeforeMonthDate() + "&end=" + GetDateUtils.getCurrentDate() + "&format=csv", header);

            Optional.ofNullable(zhiHuTrendList).orElse(new ArrayList<>()).forEach(trend -> {
                try {
                    if (zhiHuExtMapper.countTrendByExample(userName, trend.getTime()) > 0) {
                        ZhiHuTrend zhiHuTrend = zhiHuExtMapper.getTrendByUserAndTime(userName, trend.getTime());
                        trend.setUser(userName);
                        trend.setId(zhiHuTrend.getId());

                        ZhiHuTrendExample example = new ZhiHuTrendExample();
                        example.createCriteria().andIdEqualTo(zhiHuTrend.getId());
                        zhiHuTrendMapper.updateByExampleSelective(trend, example);
                    } else {
                        trend.setUser(userName);
                        trend.setId(UUID.randomUUID().toString());
                        trend.setUser(userName);
                        zhiHuTrendMapper.insert(trend);
                    }
                } catch (Exception exception) {
                    logger.error(exception.getMessage(), exception);
                }
            });
        } catch (Exception exception) {
            logger.error(user + "getAccountTrend Exception:" + exception.getMessage(), exception);
            throw exception;
        }
    }

    /*****  获取账号粉丝数据 ****/
    public void getAccountFans(User user) {
        try {
            String userName = StringUtils.isEmpty(user.getShowName()) ? user.getUserName() : user.getShowName();
            String ck = user.getCookie();
            /*调用知乎接口获取粉丝csv数据*/
            Map<String, String> header = HttpURLConnectionUtil.auth(ck);
            List<ZhiHuFans> zhiHuFansList = HttpURLConnectionUtil.doGetFans("https://www.zhihu.com/api/v4/creators/analysis/aggregation/tab/follow/detail/download?day=-90", header);

            Optional.ofNullable(zhiHuFansList).orElse(new ArrayList<>()).forEach(trend -> {
                try {
                    if (zhiHuExtMapper.countFansByExample(userName, trend.getTime()) > 0) {
                        ZhiHuFans zhiHuFans = zhiHuExtMapper.getFansByUserAndTime(userName, trend.getTime());
                        trend.setUser(userName);
                        trend.setId(zhiHuFans.getId());

                        ZhiHuFansExample example = new ZhiHuFansExample();
                        example.createCriteria().andIdEqualTo(zhiHuFans.getId());
                        zhiHuFansMapper.updateByExampleSelective(trend, example);
                    } else {
                        trend.setUser(userName);
                        trend.setId(UUID.randomUUID().toString());
                        trend.setUser(userName);
                        zhiHuFansMapper.insert(trend);
                    }
                } catch (Exception exception) {
                    logger.error(exception.getMessage(), exception);
                }
            });
        } catch (Exception exception) {
            logger.error(user + "getAccountFans Exception:" + exception.getMessage(), exception);
            throw exception;
        }
    }

    /**
     * 创建或更新知乎账号数据
     * @param user
     * @return
     */
    public Boolean createUser(User user) {
        if (user == null || StringUtils.isEmpty(user.getCookie()) || StringUtils.isEmpty(user.getUserName())) {
            return false;
        }

        UserExample example = new UserExample();
        example.createCriteria().andUserNameEqualTo(user.getUserName());
        List<User> userList = userMapper.selectByExample(example);
        if (!CollectionUtils.isEmpty(userList)) {
            User user1 = userList.get(0);
            user1.setCookie(user.getCookie());
            user1.setEmail(user.getEmail());
            user1.setOrgnization(user.getOrgnization());
            user1.setPassword(user.getPassword());
            user1.setPhone(user.getPhone());
            userMapper.updateByExample(user1, example);
        } else {
            user.setId(UUID.randomUUID().toString());
            user.setCreateTime(new Date());
            userMapper.insert(user);
        }

        return true;
    }


    /**
     * 同步所有用户的知乎回答数据(弃用)
     */
    public void syncAnswer() {
        UserExample example = new UserExample();
        List<User> userList = userMapper.selectByExample(example);
        Optional.ofNullable(userList).orElse(new ArrayList<>()).forEach(user -> {
            getAnswer(user);
        });
    }

    /**
     * 同步所有用户的知乎文章数据(弃用)
     */
    public void syncArticle() {
        UserExample example = new UserExample();
        List<User> userList = userMapper.selectByExample(example);
        Optional.ofNullable(userList).orElse(new ArrayList<>()).forEach(user -> {
            getArticle(user);
        });
    }

    /**
     * 获取数据趋势数据(弃用)
     */
    public void syncTrend() {
        UserExample example = new UserExample();
        List<User> userList = userMapper.selectByExample(example);
        Optional.ofNullable(userList).orElse(new ArrayList<>()).forEach(user -> {
            getAccountTrend(user);
        });
    }

    /**
     * 获取账号粉丝数据（弃用）
     */
    public void syncFans() {
        UserExample example = new UserExample();
        List<User> userList = userMapper.selectByExample(example);
        Optional.ofNullable(userList).orElse(new ArrayList<>()).forEach(user -> {
            getAccountFans(user);
        });
    }

}
